package com.neusoft.neuiotms.dcom.service.impl;

import java.util.List;

import javax.persistence.EntityNotFoundException;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.stereotype.Service;

import com.neusoft.bizcore.web.constant.ExceptionConstants;
import com.neusoft.bizcore.web.exception.UnitedException;
import com.neusoft.bizcore.web.support.Searchable;
import com.neusoft.neuiotms.dcom.converter.MaintainRuleConverter;
import com.neusoft.neuiotms.dcom.dto.MaintainRuleDTO;
import com.neusoft.neuiotms.dcom.model.MaintainRule;
import com.neusoft.neuiotms.dcom.model.enums.MaintainRuleStatus;
import com.neusoft.neuiotms.dcom.repository.MaintainRuleRepository;
import com.neusoft.neuiotms.dcom.repository.MaintainTaskRepository;
import com.neusoft.neuiotms.dcom.service.MaintainRuleService;

@Service
public class MaintainRuleServiceImpl implements MaintainRuleService {

    @Autowired
    private MaintainRuleRepository maintainRuleRepository;

    @Autowired
    private MaintainRuleConverter maintainRuleConventer;

    @Autowired
    private MaintainTaskRepository maintainTaskRepository;

    @Override
    public List<MaintainRuleDTO> findAll() {
        final List<MaintainRule> entity = this.maintainRuleRepository.findAll();
        final List<MaintainRuleDTO> dtos =
                this.maintainRuleConventer.toListDTO(entity);
        return dtos;
    }

    @Override
    public Page<MaintainRuleDTO> search(final Pageable pageable, final Searchable searchable) {
        final Page<MaintainRule> models = this.maintainRuleRepository.search(pageable, searchable);
        return this.maintainRuleConventer.toPageDTO(models);
    }

    @Override
    public MaintainRuleDTO create(final MaintainRuleDTO dto) {
        //        final MaintainRule checkName = this.maintainRuleRepository.findByName(dto.getName());
        //        if (checkName != null) {
        //            throw new UnitedException(ExceptionConstants.NAME_CAN_NOT_DUPLICATE, new Object[] {});
        //        }

        final MaintainRule model = this.maintainRuleConventer.toModel(dto);

        this.maintainRuleRepository.save(model);
        return this.maintainRuleConventer.toDTO(model);
    }

    @Override
    public MaintainRuleDTO update(final Long id, final MaintainRuleDTO dto) {
        MaintainRule model;
        try {
            model = this.maintainRuleRepository.getOne(id);
        } catch (final EntityNotFoundException e) {
            throw new UnitedException(ExceptionConstants.ENTITY_NOT_FOUND, new Object[] {id });
        }

        //        final MaintainRule checkName = this.maintainRuleRepository.findByName(dto.getName());
        //        if ((checkName != null) && (checkName.getId() != id)) {
        //            throw new UnitedException(ExceptionConstants.NAME_CAN_NOT_DUPLICATE, new Object[] {});
        //        }

        if (model != null) {
            dto.setId(model.getId());
        }
        model = this.maintainRuleConventer.toModel(dto);

        this.maintainRuleRepository.save(model);
        return this.maintainRuleConventer.toDTO(model);
    }

    @Override
    public MaintainRuleDTO details(final Long id) {
        final MaintainRule model;
        try {
            model = this.maintainRuleRepository.getOne(id);
        } catch (final EntityNotFoundException e) {
            throw new UnitedException(ExceptionConstants.ENTITY_NOT_FOUND, new Object[] {id });
        }
        return this.maintainRuleConventer.toDTO(model, false);
    }

    @Override
    public void delete(final Long id) {
        final Searchable searchable = new Searchable();
        searchable.put("ruleId", id);
        final Long count = this.maintainTaskRepository.getCount(searchable);
        if (count > 0) {
            throw new UnitedException(ExceptionConstants.FOREIGN_KEY_CONSTRAINT_TASK, new Object[] {id });
        }
        this.maintainRuleRepository.deleteById(id);
    }

    @Override
    public MaintainRuleDTO changeStatus(final Long id, final String flag) {
        MaintainRule model;
        try {
            model = this.maintainRuleRepository.getOne(id);
        } catch (final EntityNotFoundException e) {
            throw new UnitedException(ExceptionConstants.ENTITY_NOT_FOUND, new Object[] {id });
        }

        if (model != null) {
            model.setStatus(MaintainRuleStatus.valueOf(flag));
        }

        this.maintainRuleRepository.save(model);
        return this.maintainRuleConventer.toDTO(model);
    }

    @Override
    public List<MaintainRuleDTO> listByModelCode(final String code) {
        final List<MaintainRule> entity = this.maintainRuleRepository.findByModelCode(code);
        final List<MaintainRuleDTO> dtos =
                this.maintainRuleConventer.toListDTO(entity);
        return dtos;
    }

    @Override
    public List<MaintainRuleDTO> listByModelCodeAndStatus(final String code, final MaintainRuleStatus status) {
        final List<MaintainRule> entity = this.maintainRuleRepository.findByModelCodeAndStatus(code, status);
        final List<MaintainRuleDTO> dtos =
                this.maintainRuleConventer.toListDTO(entity);
        return dtos;
    }

}
